iT邦幫忙

2022 iThome 鐵人賽

DAY 19
0
Mobile Development

Android Studio 30天學習紀錄系列 第 19

Android Studio 30天學習紀錄-Day19 java&kt執行緒使用

  • 分享至 

  • xImage
  •  

Thread執行緒,往往在執行耗時程序的時候會使用到,若都由主執行緒來執行,可能會導致阻塞很久無法繼續運作,多執行緒的能力還是有效提高了程式執行的效率及使用者體驗,但通常還是盡量減少執行緒的數量,因為還是會些微影響系統的速度及記憶體空間,那麼首先先進入到java的執行緒。

Java(Thread、Handler)

Thread方法:

  • start:執行緒開始
  • join :封鎖呼叫執行緒,先等待此執行緒完成才往下
  • sleep(ms) :延時多少毫秒
  • wait() :使該執行緒進入等待狀態
  • wait(time):指定等待時間,當沒notify喚醒他則時間到會自動喚醒
  • notify():喚醒該執行緒
  • notifyAll():喚醒所有等待狀態中的執行緒

因為android在執行緒中修改ui的話是不被允許的,但可以透過Looper、runOnUiThread在執行緒中更新你的ui。

Thread thread = new Thread(new Runnable() {
    @Override
    public void run() {
        Looper.prepare();
        Toast.makeText(getApplicationContext(),"abc",Toast.LENGTH_SHORT).show();
        Looper.loop();
//        runOnUiThread(()->{
//            Toast.makeText(getApplicationContext(),"cba",Toast.LENGTH_SHORT).show();
//        });
    }
});
//執行緒開始
thread.start();
//isAlive 判斷目前執行緒是否執行中
Log.d("Thread",""+thread.isAlive());
        //當有多個執行緒時,使用join會有中斷問題(InterruptedException)
//        try {
//            thread.join();
//            ...join
//        } catch (InterruptedException e) {
//            e.printStackTrace();
//        }

Handler方法:

與Thread一樣也會去實作Runnable的run方法運行,也有wait與notify的方法,我自己是比較常用到以下的兩種執行handler的寫法:

        //Handler
        Handler handler = new Handler();
        //無延遲執行
        handler.post(new Runnable() {
            @Override
            public void run() {
                Toast.makeText(getApplicationContext(),"handler1!",Toast.LENGTH_SHORT).show();
            }
        });
        //延遲1秒執行
        handler.postDelayed(new Runnable() {
            @Override
            public void run() {
                Toast.makeText(getApplicationContext(),"handler2!",Toast.LENGTH_SHORT).show();
            }
        },1000);

而另外也有許多會用到message的方法,如果想了解更多的可以點這邊:Android Developers


Kotlin(Coroutines)

Coroutines(協程),與Thread類似,比較不同的是:協程是協作式處理,線程Thread是搶佔式處理,協程可透過其他協程的調用來進行轉換(會保持狀態),以此來並行運作,大約有runBlocking,coroutineScope,withContext等
,另外也有asyncTask能用來處理耗時任務,接著就簡單的進行使用:

class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        //runBlocking(阻塞的coroutine)
        runBlocking {
            //launch為內部、順序執行
            launch{
                Log.d("LOGTAG","runBlocking1")
            }
            launch{
                Log.d("LOGTAG","runBlocking2")
            }
        }
        //coroutineScope launch(內部新增一個協程,順序執行)
        GlobalScope.launch {
            Log.d("LOGTAG","GlobalScope")
        }
        //Dispatchers.Main=主線程執行
        CoroutineScope(Dispatchers.Main).launch{
            Log.d("LOGTAG","CoroutineScope")
        }
        //Dispatchers.Default=預設(不會跑在主線程)
        CoroutineScope(Dispatchers.Default).launch {
            abc()
        }
    }
}
//withContext可切換Dispatcher
suspend fun abc() = withContext(Dispatchers.Default) {
    Log.d("LOGTAG","withContext")
}

假如這些coroutines的關鍵字是紅字的話,可能需要在gradle內加入coroutines的依賴:

依賴

implementation "org.jetbrains.kotlinx:kotlinx-coroutines-core:1.0.0"
implementation "org.jetbrains.kotlinx:kotlinx-coroutines-android:1.0.0"

成果

https://ithelp.ithome.com.tw/upload/images/20220930/20139259uJybZif7w7.jpg


上一篇
Android Studio 30天學習紀錄-Day18 Kotlin&基礎語法
下一篇
Android Studio 30天學習紀錄-Day 20 MvvM
系列文
Android Studio 30天學習紀錄30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言